package io.gitee.zhangbinhub.acp.boot.ftp.init.task

import io.gitee.zhangbinhub.acp.boot.ftp.base.BaseInitFtpServer
import io.gitee.zhangbinhub.acp.boot.ftp.conf.AcpFtpServerConfiguration
import io.gitee.zhangbinhub.acp.boot.ftp.server.AcpFtpServer
import io.gitee.zhangbinhub.acp.boot.ftp.user.UserFactory
import io.gitee.zhangbinhub.acp.core.common.interfaces.IDaemonService
import io.gitee.zhangbinhub.acp.core.common.log.LogFactory
import java.lang.reflect.InvocationTargetException

/**
 * @since JDK 17
 */
object InitFtpServer : BaseInitFtpServer() {

    /**
     * 日志对象
     */
    private val log = LogFactory.getInstance(InitFtpServer::class.java)

    @JvmStatic
    fun startFtpServer(
        acpFtpServerConfiguration: AcpFtpServerConfiguration,
        userFactory: MutableMap<String, UserFactory>?
    ): List<IDaemonService> {
        log.info("start ftp servers ...")
        userFactory?.forEach { entity -> addUserFactory(entity.key, entity.value) }
        var ftpServers: List<IDaemonService> = ArrayList()
        try {
            ftpServers = doStart(acpFtpServerConfiguration)
        } catch (e: Exception) {
            log.error(e.message, e)
            log.info("start ftp servers exception: " + e.message)
        }
        return ftpServers
    }

    @Throws(
        ClassNotFoundException::class,
        NoSuchMethodException::class,
        IllegalAccessException::class,
        InvocationTargetException::class,
        InstantiationException::class
    )
    private fun doStart(acpFtpServerConfiguration: AcpFtpServerConfiguration): List<IDaemonService> {
        val ftpServers = ArrayList<IDaemonService>()
        val listeners = acpFtpServerConfiguration.listeners
        if (listeners.isNotEmpty()) {
            for (listen in listeners) {
                if (listen.enabled) {
                    val beanName = listen.userFactoryBean
                    getUserFactory(beanName)?.let { userFactory ->
                        val acpFtpServer = AcpFtpServer(userFactory.generateFtpUserList(), listen)
                        val sub = Thread(acpFtpServer)
                        sub.isDaemon = true
                        sub.start()
                        ftpServers.add(acpFtpServer)
                    } ?: log.error("start ftp server failed [" + listen.name + "] : user factory bean is null")
                } else {
                    log.info("ftp server is disabled [" + listen.name + "]")
                }
            }
        } else {
            log.info("No ftp service was found")
        }
        return ftpServers
    }
}